﻿using System;
using System.IO;

namespace MultiViewer.Display
{
    public static class Utils
    {
        public static int GetDisplayRow(int nodeId, int gridWidth, int gridHeight)
        {
            if (nodeId < 1 || nodeId > gridWidth * gridHeight)
                throw new ArgumentException("Node id is out of range", "nodeId");
            return (nodeId - 1) / gridWidth;
        }

        public static int GetDisplayColumn(int nodeId, int gridWidth, int gridHeight)
        {
            if (nodeId < 1 || nodeId > gridWidth * gridHeight)
                throw new ArgumentException("Node id is out of range", "nodeId");
            return (nodeId - 1) % gridWidth;
        }

        static public void CopyStream(Stream dst, Stream src)
        {
            byte[] buffer = new byte[4096];
            while (true)
            {
                int bytesRead = src.Read(buffer, 0, 4096);
                if (bytesRead > 0)
                    dst.Write(buffer, 0, bytesRead);
                else
                    break;
            }
        }

        public static Rect ZoomIn(Rect visible)
        {
            double centerY = (visible.Bottom + visible.Top) / 2;
            double centerX = (visible.Left + visible.Right) / 2;

            double width = visible.Right - visible.Left;
            double height = visible.Top - visible.Bottom;

            return new Rect
            {
                Left = centerX - width / 4,
                Right = centerX + width / 4,
                Bottom = centerY - height / 4,
                Top = centerY + height / 4,
            };
        }

        public static Rect ZoomOut(Rect visible, Rect entireImage)
        {
            double centerY = (visible.Bottom + visible.Top) / 2;
            double centerX = (visible.Left + visible.Right) / 2;

            double width = visible.Right - visible.Left;
            double height = visible.Top - visible.Bottom;

            if (width >= entireImage.Width || height >= entireImage.Height)
                return visible;

            visible.Left = centerX - width;
            visible.Right = centerX + width;
            visible.Bottom = centerY - height;
            visible.Top = centerY + height;

            if (visible.Left < entireImage.Left)
            {
                visible.Right += entireImage.Left - visible.Left;
                visible.Left = entireImage.Left;
            }

            if (visible.Right > entireImage.Right)
            {
                visible.Left -= visible.Right - entireImage.Right;
                visible.Right = entireImage.Right;
            }

            if (visible.Top > entireImage.Top)
            {
                visible.Bottom -= visible.Top - entireImage.Top;
                visible.Top = entireImage.Top;
            }

            if (visible.Bottom < entireImage.Bottom)
            {
                visible.Top += entireImage.Bottom - visible.Bottom;
                visible.Bottom = entireImage.Bottom;
            }

            return visible;
        }
     
        public static Rect Pan(Rect visible, Rect entireImage, double xShift, double yShift)
        {
            if (visible.Left + xShift < entireImage.Left)
                xShift = entireImage.Left - visible.Left;
            if (visible.Right + xShift > entireImage.Right)
                xShift = entireImage.Right - visible.Right;

            if (visible.Bottom + yShift < entireImage.Bottom)
                yShift = entireImage.Bottom - visible.Bottom;
            if (visible.Top + yShift > entireImage.Top)
                yShift = entireImage.Top - visible.Top;

            visible.Left += xShift;
            visible.Right += xShift;

            visible.Top += yShift;
            visible.Bottom += yShift;

            return visible;
        }

/*        public void MoveTo(double x, double y)
        {
            double dx = (x - visible.Width / 2) - visible.Left;
            double dy = (y + visible.Height / 2) - visible.Top;

            ShiftClientFrames(dx, dy);
        }


        public void ZoomOut()
        {
            double centerY = (visible.Bottom + visible.Top) / 2;
            double centerX = (visible.Left + visible.Right) / 2;

            double width = visible.Right - visible.Left;
            double height = visible.Top - visible.Bottom;

            if (width >= entireImage.Width || height >= entireImage.Height)
                return;

            visible.Left = centerX - width;
            visible.Right = centerX + width;
            visible.Bottom = centerY - height;
            visible.Top = centerY + height;

            if (visible.Left < entireImage.Left)
            {
                visible.Right += entireImage.Left - visible.Left;
                visible.Left = entireImage.Left;
            }

            if (visible.Right > entireImage.Right)
            {
                visible.Left -= visible.Right - entireImage.Right;
                visible.Right = entireImage.Right;
            }

            if (visible.Top > entireImage.Top)
            {
                visible.Bottom -= visible.Top - entireImage.Top;
                visible.Top = entireImage.Top;
            }

            if (visible.Bottom < entireImage.Bottom)
            {
                visible.Top += entireImage.Bottom - visible.Bottom;
                visible.Bottom = entireImage.Bottom;
            }

            UpdateClientFrames();
        }


        public void PanUp()
        {
            ShiftClientFrames(0, (visible.Top - visible.Bottom) / 5);
        }

        public void PanDown()
        {
            ShiftClientFrames(0, -(visible.Top - visible.Bottom) / 5);
        }

        public void PanLeft()
        {
            ShiftClientFrames(-(visible.Right - visible.Left) / 5, 0);
        }

        public void PanRight()
        {
            ShiftClientFrames((visible.Right - visible.Left) / 5, 0);
        }
*/
    }
}